home *** CD-ROM | disk | FTP | other *** search
- /*******************************************************************************
- *
- * Program: ExecuteOnReset
- * Filename: ExecuteOnReset.c
- *
- * Usage: Run <>NIL: ExecuteOnReset [-p pri] string1 [string2] ...
- * -p pri - priority (default: 0)
- * string1 - command line 1 to execute
- * string2 - optional command line 2 to execute
- * ... - more command lines.
- *
- * Contents: Installes a reset handler which executes the command
- * lines on case of a reset (CTRL-Amiga-Amiga). After
- * execution of all commands the handler continues with
- * the reset (or other installed reset handlers)
- * imediately! So if you do some disk tasks add a
- * "Wait 3 secs" line as last command to avoid non
- * validated disks. You must be cautionous: The Amiga
- * allows a maximum of 10 seconds to do all reset handler
- * tasks. After this amount of time a hard reset occurs
- * regardless if a command has finished or not. If you
- * install more reset handlers you can choose the order
- * of execution by the priority argument.
- * The Run command is necessary to detach from the shell.
- * A CTRL-C signal removes the handler.
- *
- * Language: C
- *
- * Link-instr.: Objects: c.o ExecuteOnReset.o keyhandler.o
- * Libraries: amiga.lib
- * Output: ExecuteOnReset
- *
- * Author: Johannes R. Geiss
- *
- * Copyright: Amigavisions
- *
- * History: $HISTORY:
- *
- * 08 Aug 2000 : 001.001 : written jgeiss
- *
- * Version: $VER: ExecuteOnReset 1.001 (08 Aug 2000)
- *
- *******************************************************************************/
-
-
- /**************/
- /*- Includes -*/
-
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
-
- #include <exec/types.h>
- #include <exec/interrupts.h>
- #include <dos/dos.h>
- #include <devices/keyboard.h>
- #include <clib/exec_protos.h>
- #include <clib/alib_protos.h>
-
-
- /*************/
- /*- Imports -*/
-
- extern void ResetHandler();
-
-
- /*****************/
- /*- Definitions -*/
-
- #define VER "1.1"
-
- #define CSI "\x9b"
- #define COLORBOLD CSI "1;33m"
- #define COLOR CSI "0;33m"
- #define NORMAL CSI "0m"
-
-
- /*************/
- /*- Structs -*/
-
- struct MyData
- {
- struct Task *MyTask;
- ULONG MySignal;
- };
-
-
- /**********/
- /*- main -*/
-
- int main(int argc, char *argv[])
- {
- BYTE pri = 0;
- int i, start;
- UWORD len;
- char *command;
- int rc = 0;
- ULONG MySignal;
- struct MyData MyDataStuff;
- struct Interrupt *keyHandler;
- struct IOStdReq *keyReqBlk;
-
-
- /*
- * handle arguments
- */
-
- i = 1;
-
- if((argc > i) && (!strcmp(argv[i], "?"))) {
- printf("\n"
- COLORBOLD "ExecuteOnReset V" VER ":" COLOR " Copyright (C) 2000, Amigavisions" NORMAL "\n"
- "Usage: Run <>NIL: %s [-p pri] string1 [string2] ...\n"
- " -p pri - priority (default: 0)\n"
- " string1 - command line 1 to execute\n"
- " string2 - optional command line 2 to execute\n"
- " ... - more command lines.\n"
- "Installes a reset handler which executes the command lines on case of a reset\n"
- "(CTRL-Amiga-Amiga). After execution of all commands the handler continues with\n"
- "the reset (or other installed reset handlers) imediately! So if you do some disk\n"
- "tasks add a \"Wait 3 secs\" line as last command to avoid non validated disks.\n"
- "You must be cautionous: The Amiga allows a maximum of 10 seconds to do all reset\n"
- "handler tasks. After this amount of time a hard reset occurs regardless if a\n"
- "command has finished or not. If you install more reset handlers you can choose\n"
- "the order of execution by the priority argument.\n"
- "The Run command is necessary to detach from the shell. A CTRL-C signal removes\n"
- "the handler.\n"
- "\n", argv[0]);
- return 5;
- }
-
- if((argc > i) && (argv[i][0] == '-')) {
-
- if(argv[i][1] == 'p') {
-
- if(argv[i][2]) pri = atoi(&argv[i++][2]);
- else if(argc > ++i) pri = atoi(argv[i++]);
- else {
- fprintf(stderr, "%s: missing priority\n", argv[0]);
- return 10;
- }
-
- }
- else {
- fprintf(stderr, "%s: unknown option: -%c\n", argv[0], argv[i][1]);
- return 11;
- }
-
- }
-
- start = i;
- len = 0;
-
- while(i < argc) len += strlen(argv[i++]) + 1;
-
- if(len == 0) {
- fprintf(stderr, "%s: missing command line\n", argv[0]);
- return 12;
- }
-
-
- /*
- * create command
- */
-
- if(command = AllocMem(len, MEMF_PUBLIC|MEMF_CLEAR)) {
- i = start;
-
- while(i < argc) {
- strcat(command, argv[i++]);
- strcat(command, "\n");
- }
-
-
- /*
- * install reset handler
- */
-
- if((MySignal = AllocSignal(-1l)) != -1) {
- MyDataStuff.MyTask = FindTask(NULL);
- MyDataStuff.MySignal = 1l << MySignal;
-
- if(keyHandler = AllocMem(sizeof(struct Interrupt),
- MEMF_PUBLIC|MEMF_CLEAR)) {
-
- if(keyReqBlk = (struct IOStdReq *)
- CreateExtIO(CreatePort(NULL, 0), sizeof(struct IOStdReq))) {
-
- if(!(OpenDevice("keyboard.device", NULL,
- (struct IORequest *)keyReqBlk, NULL))) {
- keyHandler->is_Code = ResetHandler;
- keyHandler->is_Data = (APTR)&MyDataStuff;
- keyHandler->is_Node.ln_Pri = pri;
- keyHandler->is_Node.ln_Name = argv[0];
- keyReqBlk->io_Data = (APTR)keyHandler;
- keyReqBlk->io_Command = KBD_ADDRESETHANDLER;
- DoIO((struct IORequest *)keyReqBlk);
-
-
- /*
- * wait for reset or CTRL-C
- */
-
- if(Wait(MyDataStuff.MySignal|SIGBREAKF_CTRL_C)
- & MyDataStuff.MySignal) {
-
-
- /*
- * captured a reset
- * now execute the command(s)
- */
-
- system(command);
-
-
- /*
- * tell reset handler we are finished
- * so others can do their job
- */
-
- keyReqBlk->io_Data = (APTR)keyHandler;
- keyReqBlk->io_Command = KBD_RESETHANDLERDONE;
- DoIO((struct IORequest *)keyReqBlk);
-
-
- /*
- * wait for reset
- */
-
- Wait(0l);
- }
-
-
- /*
- * got a CTRL-C
- * so we remove ourself
- */
-
- keyReqBlk->io_Data = (APTR)keyHandler;
- keyReqBlk->io_Command = KBD_REMRESETHANDLER;
- DoIO((struct IORequest *)keyReqBlk);
-
- CloseDevice((struct IORequest *)keyReqBlk);
- }
- else {
- fprintf(stderr, "%s: couldn't open keyboard device\n", argv[0]);
- rc = 24;
- }
-
- }
- else {
- fprintf(stderr, "%s: couldn't create keyboard io\n", argv[0]);
- rc = 23;
- }
-
- FreeMem(keyHandler, sizeof(struct Interrupt));
- }
- else {
- fprintf(stderr, "%s: couldn't allocate memory\n", argv[0]);
- rc = 22;
- }
-
- FreeSignal(MySignal);
- }
- else {
- fprintf(stderr, "%s: couldn't allocate signal\n", argv[0]);
- rc = 21;
- }
-
- FreeMem(command, len);
- }
- else {
- fprintf(stderr, "%s: couldn't allocate memory\n", argv[0]);
- rc = 20;
- }
-
-
- /*
- * exit
- */
-
- return rc;
- }
-
-
- /** EOF **/
-
-